<template>
    <a-tree v-bind="treeOption"
            v-on="treeEvent"
            v-model:expanded-keys="expandedKeys">
        <template #switcher-icon="node">
            <icon-plus  v-if="!nodeIcon(node)" />
            <icon-minus v-else />
        </template>
        <template #loading-icon>
            <icon-loading />
        </template>
        <!-- 如果有自定义节点 ， 使用插槽自定义节点 -->
        <template v-if="slots.hasOwnProperty('node')" #title="nodeData">
            <slot name="node" :data="nodeData"/>
        </template>
    </a-tree>
</template>
<script setup>
    // 获取外部传参
    const props=defineProps({
        // 组件的静态渲染数据
        data:{
            type:Array,
            default:()=>[]
        },
        // 组件的原生官方配置
        defineProps:{
            type:Object,
            default:()=>({})
        },
        // 开启懒加载
        load:{
            type:Object,
            default:()=>({})
        },
    })
    const slots = useSlots();
    // 当前展开的节点
    const expandedKeys = ref([])
    // 一个计算属性 ref , 用来判断当前节点的展开状态
    const nodeIcon = computed(() => {
        return (node)=>{
            let key = 'key'
            // 如果设置了自定义字段 ，使用自定义的key 来进行匹配
            if(props?.defineProps?.fieldNames){
                key = props.defineProps.fieldNames['key']
            }
            return expandedKeys.value.includes(node[key])
        }
    })
    // 树组件的默认配置
    const defaultOptions = {
        class:'hk_tree',
        blockNode:true
    }
    // 树组件的响应式配置
    const treeOption = reactive({})
    const treeEvent = ref({})
    // 初始化组件配置
    onMounted(()=>{
        setOptions()
    })
    // 根据外部props ， 设置组件的渲染类型
    const setOptions=async ()=>{
        const { data , load , defineProps} = props
        // props 配置
        const option = {
            ...defaultOptions,
        }

        // 事件配置
        const event = {}

        // 通过循环 ， 将 配置与事件 分离开来 ， v-bing 绑定配置 ， v-on 绑定事件
        for(let k in defineProps){
            if(typeof defineProps[k] === 'function' ){
                event[k] = defineProps[k]
            }else{
                option[k] = defineProps[k]
            }
        }
        // 使用静态数据data   PS:需要深拷贝，否则无法响应式
        if(data){
            option.data = JSON.parse(JSON.stringify(data))
        }
        // 如果开启了远程加载 ， 将使用远程加载数据 , 此时静态数据无效
        if( load?.query && load?.setParams ){
            const params = load.setParams()
            const res = await load.query(params)
            option.data = res
            option.loadMore = loadMore
        }
        treeEvent.value = event
        for(let k in option ){
            treeOption[k] = option[k]
        }
    }
    // 数据懒加载 ， 开启 props.load 后生效
    const loadMore = (nodeData) => {
        const { query , setParams } = props.load
        return new Promise(async (resolve) => {
            const params = setParams(nodeData)
            const res = await query(params,nodeData)
            nodeData.children = res
            resolve()
        });
    };

</script>

<style lang="less" scoped>
    .hk_tree{

        @textColor:#02a7fd;
        @hoverTextColor:#0bf4e4;
        @bgColor:#085371;
        @disabledColor:#3f6292;

        ::v-deep{
            .arco-tree-node{
                color:@textColor;
                padding-left: .1rem;
                display: flex;
                overflow: hidden;

                .arco-tree-node-title{
                    flex: 1;
                    overflow: hidden;
                    .arco-tree-node-title-text{
                        overflow: hidden;
                        white-space: nowrap;
                        text-overflow: ellipsis;
                    }
                    &.arco-tree-node-title-highlight{
                        color: @hoverTextColor;
                        background-color: transparent;
                    }
                }

                .arco-tree-node-switcher{
                    color:@textColor;
                    .arco-icon-hover{
                       // transform: rotate(90deg);
                        &:before{
                            background-color: transparent;
                        }
                    }
                }

                &.arco-tree-node-selected , &:hover{
                    position: relative;
                   // border-left: .03rem solid #0bf4e4;
                    background-color: @bgColor;
                    .arco-tree-node-title-highlight, .arco-tree-node-title, .arco-tree-node-title:hover , .arco-tree-node-title:focus{
                         color: @hoverTextColor;
                         background-color: transparent;
                     }
                    &:before{
                        position: absolute;
                        content: '';
                        display: block;
                        height: 100%;
                        width:.03rem;
                        top: 0;
                        left: 0;
                        bottom: 0;
                        background-color:@hoverTextColor ;
                    }
                }

                &.arco-tree-node-disabled , .arco-tree-node-disabled-selectable{
                     .arco-tree-node-title, .arco-tree-node-title:hover {
                         color:@disabledColor;
                     }
                }


            }
        }
    }

</style>